<template>
  <div class="knowledge-base-container">
    <!-- 返回按钮 -->
    <button @click="goBack" class="back-button" title="返回聊天">
      <svg
        viewBox="0 0 24 24"
        fill="none"
        stroke="currentColor"
        stroke-width="2"
      >
        <path d="M19 12H5M12 19l-7-7 7-7" />
      </svg>
      <span>返回</span>
    </button>

    <div class="knowledge-base-content">
      <!-- 搜索区域 -->
      <div class="search-section">
        <el-input
          v-model="searchKeyword"
          placeholder="请输入关键词进行查询"
          class="search-input"
          clearable
          @keyup.enter="handleSearch"
        >
          <template #prefix>
            <el-icon><Search /></el-icon>
          </template>
        </el-input>
        <el-button type="primary" @click="handleSearch">查询</el-button>
        <el-button @click="handleClear">清空</el-button>
      </div>

      <!-- 表格区域 -->
      <div class="table-section">
        <div class="table-wrapper">
          <el-table
            :data="tableData"
            stripe
            border
            style="width: 100%"
            :empty-text="'暂无数据'"
            v-loading="loading"
          >
            <el-table-column prop="id" label="ID" width="80" align="center">
              <template #default="{ row }">
                {{ row.id }}
              </template>
            </el-table-column>
            <el-table-column prop="title" label="标题" min-width="200">
              <template #default="{ row }">
                {{ row.title }}
              </template>
            </el-table-column>
            <el-table-column prop="file_info" label="文件信息" min-width="250">
              <template #default="{ row }">
                <div v-if="row.file_info" class="file-info-cell">
                  <div class="file-name-row">
                    <el-icon class="file-icon"><Document /></el-icon>
                    <span class="file-name" :title="row.file_info.filename">
                      {{ row.file_info.filename || "未命名文件" }}
                    </span>
                  </div>
                  <div class="file-meta-row">
                    <span class="file-type">{{
                      getFileTypeLabel(row.file_info.file_type)
                    }}</span>
                    <span class="file-separator">|</span>
                    <span class="file-date">{{
                      formatDate(row.file_info.uploaded_at)
                    }}</span>
                  </div>
                </div>
                <span v-else class="no-file">暂无文件</span>
              </template>
            </el-table-column>
            <el-table-column prop="status" label="状态" width="120" align="center">
              <template #default="{ row }">
                <el-tag :type="getStatusTagType(row.status || row.file_info?.status)" size="small">
                  {{ getStatusLabel(row.status || row.file_info?.status) }}
                </el-tag>
              </template>
            </el-table-column>
            <el-table-column prop="created_at" label="创建时间" width="180">
              <template #default="{ row }">
                {{ formatDate(row.created_at) }}
              </template>
            </el-table-column>
            <el-table-column prop="updated_at" label="更新时间" width="180">
              <template #default="{ row }">
                {{ formatDate(row.updated_at) }}
              </template>
            </el-table-column>
            <el-table-column label="操作" width="240" fixed="right">
              <template #default="{ row }">
                <el-button
                  v-if="row.file_info && row.file_info.filepath"
                  type="success"
                  size="small"
                  @click="handleDownload(row)"
                >
                  下载
                </el-button>
                <el-button type="primary" size="small" @click="handleEdit(row)">
                  编辑
                </el-button>
                <el-button
                  type="danger"
                  size="small"
                  @click="handleDelete(row)"
                >
                  删除
                </el-button>
              </template>
            </el-table-column>
          </el-table>
        </div>

        <!-- 分页组件 -->
        <div class="pagination-wrapper">
          <el-pagination
            v-model:current-page="pagination.page"
            v-model:page-size="pagination.pageSize"
            :page-sizes="[10, 20, 50, 100]"
            :total="pagination.total"
            layout="total, sizes, prev, pager, next, jumper"
            @size-change="handleSizeChange"
            @current-change="handlePageChange"
          />
        </div>

        <!-- 添加按钮 -->
        <div class="add-button-wrapper">
          <el-button
            type="primary"
            size="large"
            @click="handleAdd"
            class="add-button"
          >
            <el-icon><Plus /></el-icon>
            新增知识库
          </el-button>
        </div>
      </div>
    </div>

    <!-- 新增/编辑对话框 -->
    <el-dialog
      v-model="dialogVisible"
      :title="dialogTitle"
      width="600px"
      :close-on-click-modal="false"
    >
      <el-form
        ref="formRef"
        :model="formData"
        :rules="formRules"
        label-width="80px"
        label-position="left"
        :disabled="isUploading"
      >
        <el-form-item label="标题" prop="title">
          <el-input
            v-model="formData.title"
            placeholder="请输入标题"
            clearable
          />
        </el-form-item>
        <el-form-item label="附件">
          <el-upload
            v-model:file-list="formData.fileList"
            :limit="1"
            accept=".doc,.docx,.xls,.xlsx,.pdf,.ppt,.pptx,.txt"
            :on-exceed="handleExceed"
            :on-remove="handleRemove"
            :before-upload="beforeUpload"
            :http-request="handleUploadRequest"
            :on-success="handleUploadSuccess"
            :on-error="handleUploadError"
            drag
            class="upload-demo"
          >
            <el-icon class="el-icon--upload"><upload-filled /></el-icon>
            <div class="el-upload__text">
              将文件拖到此处，或<em>点击上传</em>
            </div>
            <template #tip>
              <div class="el-upload__tip">
                支持 word/excel/pdf/ppt/txt 格式，单个文件大小不超过 100MB
              </div>
            </template>
          </el-upload>
        </el-form-item>
      </el-form>
      <template #footer>
        <span class="dialog-footer">
          <el-button @click="dialogVisible = false" :disabled="isUploading"
            >取消</el-button
          >
          <el-button
            type="primary"
            @click="handleSubmit"
            :loading="isUploading"
            :disabled="isUploading"
          >
            {{ isUploading ? "上传中..." : "确定" }}
          </el-button>
        </span>
      </template>
    </el-dialog>
  </div>
</template>

<script setup>
import { ref, onMounted, nextTick } from "vue";
import { useRouter } from "vue-router";
import { ElMessage, ElMessageBox } from "element-plus";
import {
  Search,
  Plus,
  UploadFilled,
  Document,
  Download,
} from "@element-plus/icons-vue";
import {
  uploadKnowledgeAttachment,
  createKnowledge,
  getKnowledgeList,
  updateKnowledge,
  deleteKnowledge,
  downloadKnowledgeFile,
} from "@/api/knowledge";

// ==================== 初始化 ====================
const router = useRouter();

// ==================== 常量定义 ====================
const MAX_FILE_SIZE = 100 * 1024 * 1024; // 100MB
const ALLOWED_EXTENSIONS = [".doc", ".docx", ".xls", ".xlsx", ".pdf", ".ppt", ".pptx", ".txt"];
const FILE_TYPE_MAP = {
  "application/pdf": "PDF",
  "application/msword": "Word",
  "application/vnd.openxmlformats-officedocument.wordprocessingml.document": "Word",
  "application/vnd.ms-excel": "Excel",
  "application/vnd.openxmlformats-officedocument.spreadsheetml.sheet": "Excel",
  "application/vnd.ms-powerpoint": "PowerPoint",
  "application/vnd.openxmlformats-officedocument.presentationml.presentation": "PowerPoint",
  "text/plain": "文本",
};

// ==================== 组件状态 ====================
// 搜索和列表
const searchKeyword = ref("");
const tableData = ref([]);
const loading = ref(false);

// 分页
const pagination = ref({
  page: 1,
  pageSize: 10,
  total: 0,
  pages: 0,
  hasPrev: false,
  hasNext: false,
});

// 对话框和表单
const dialogVisible = ref(false);
const dialogTitle = ref("新增知识库");
const formRef = ref(null);
const formData = ref({
  id: null,
  title: "",
  attachments: [],
  fileList: [],
});

// 文件上传
const isUploading = ref(false);

// ==================== 表单验证规则 ====================
const formRules = {
  title: [
    { required: true, message: "请输入标题", trigger: "blur" },
    {
      min: 1,
      max: 100,
      message: "标题长度在 1 到 100 个字符",
      trigger: "blur",
    },
  ],
};

// ==================== 工具函数 ====================
const normalizeAttachment = (item) => ({
  id: item?.id ?? item?.response?.id ?? null,
  filename: item?.filename ?? item?.name ?? item?.response?.filename ?? "",
  file_type: item?.file_type ?? item?.response?.file_type ?? "",
  filepath: item?.filepath ?? item?.url ?? item?.response?.filepath ?? "",
  uploaded_at: item?.uploaded_at ?? item?.response?.uploaded_at ?? "",
  is_active: item?.is_active ?? item?.response?.is_active ?? true,
});

const toUploadFile = (attachment) => ({
  name: attachment.filename || attachment.name || "未命名文件",
  url: attachment.filepath,
  status: "success",
  uid:
    attachment.id !== undefined
      ? String(attachment.id)
      : `temp-${Date.now()}-${Math.random()}`,
  response: attachment,
});

const formatDate = (dateString) => {
  if (!dateString) return "-";
  const date = new Date(dateString);
  return date.toLocaleString("zh-CN", {
    year: "numeric",
    month: "2-digit",
    day: "2-digit",
    hour: "2-digit",
    minute: "2-digit",
  });
};

const getFileTypeLabel = (fileType) => {
  if (!fileType) return "未知类型";
  return FILE_TYPE_MAP[fileType] || fileType.split("/").pop() || "未知类型";
};

const getStatusLabel = (status) => {
  if (status === undefined || status === null || status === "") {
    return "上传成功";
  }
  const statusMap = {
    1: "解析中",
    2: "解析完成",
    3: "解析失败",
  };
  return statusMap[status] || "未知状态";
};

const getStatusTagType = (status) => {
  if (status === undefined || status === null || status === "") {
    return "success";
  }
  const typeMap = {
    1: "warning", // 解析中 - 黄色
    2: "success", // 解析完成 - 绿色
    3: "danger",  // 解析失败 - 红色
  };
  return typeMap[status] || "info";
};

const extractTitleFromFilename = (filename) => {
  if (!filename) return "";
  const lastDotIndex = filename.lastIndexOf(".");
  if (lastDotIndex > 0) {
    return filename.substring(0, lastDotIndex);
  }
  return filename;
};

// ==================== 列表管理 ====================
const loadKnowledgeList = async () => {
  loading.value = true;
  try {
    const response = await getKnowledgeList(
      pagination.value.page,
      pagination.value.pageSize,
      searchKeyword.value
    );
    tableData.value = response.list || [];
    pagination.value = {
      page: response.page || pagination.value.page,
      pageSize: response.page_size || pagination.value.pageSize,
      total: response.total || 0,
      pages: response.pages || 0,
      hasPrev: response.has_prev || false,
      hasNext: response.has_next || false,
    };
  } catch (error) {
    console.error("加载知识库列表失败", error);
    ElMessage.error("加载知识库列表失败，请重试");
    tableData.value = [];
  } finally {
    loading.value = false;
  }
};

const handleSearch = () => {
  pagination.value.page = 1;
  loadKnowledgeList();
};

const handleClear = () => {
  searchKeyword.value = "";
  pagination.value.page = 1;
  loadKnowledgeList();
};

const handleSizeChange = (size) => {
  pagination.value.pageSize = size;
  pagination.value.page = 1;
  loadKnowledgeList();
};

const handlePageChange = (page) => {
  pagination.value.page = page;
  loadKnowledgeList();
};

// ==================== CRUD 操作 ====================
const handleDownload = async (row) => {
  if (!row.file_info?.filepath) {
    ElMessage.warning("文件路径不存在，无法下载");
    return;
  }
  try {
    await downloadKnowledgeFile(row.file_info.filepath, row.file_info.filename);
    ElMessage.success("文件下载成功");
  } catch (error) {
    console.error("下载文件失败", error);
    ElMessage.error("下载文件失败，请重试");
  }
};

const handleAdd = () => {
  dialogTitle.value = "新增知识库";
  formData.value = {
    id: null,
    title: "",
    attachments: [],
    fileList: [],
  };
  dialogVisible.value = true;
  nextTick(() => {
    formRef.value?.clearValidate();
  });
};

const handleEdit = (row) => {
  dialogTitle.value = "编辑知识库";
  const attachments = row.file_info
    ? [
        {
          id: row.file_info.id,
          filename: row.file_info.filename || "未命名文件",
          file_type: row.file_info.file_type || "",
          filepath: row.file_info.filepath || "",
          uploaded_at: row.file_info.uploaded_at || row.updated_at || row.created_at,
          is_active: row.file_info.is_active !== false,
        },
      ]
    : [];
  formData.value = {
    id: row.id,
    title: row.title,
    attachments,
    fileList: attachments.map((item) => toUploadFile(item)),
  };
  dialogVisible.value = true;
  nextTick(() => {
    formRef.value?.clearValidate();
  });
};

const handleDelete = async (row) => {
  try {
    await ElMessageBox.confirm(`确定要删除"${row.title}"吗？`, "删除确认", {
      confirmButtonText: "确定",
      cancelButtonText: "取消",
      type: "warning",
    });
    await deleteKnowledge(row.id);
    ElMessage.success("删除成功");
    if (tableData.value.length === 1 && pagination.value.page > 1) {
      pagination.value.page--;
    }
    loadKnowledgeList();
  } catch (error) {
    if (error !== "cancel" && error !== "close") {
      console.error("删除失败", error);
      ElMessage.error("删除失败，请重试");
    }
  }
};

// ==================== 表单提交 ====================
const validateFileUpload = () => {
  const hasUploadingFile = formData.value.fileList.some(
    (file) => file.status === "uploading"
  );
  if (hasUploadingFile || isUploading.value) {
    ElMessage.warning("文件正在上传中，请等待上传完成后再提交");
    return false;
  }
  return true;
};

const getFileId = () => {
  const uploadedFile = formData.value.fileList.find(
    (file) => file.status === "success" && file.response?.id
  );
  if (uploadedFile?.response?.id) {
    return uploadedFile.response.id;
  }
  if (formData.value.attachments.length > 0 && formData.value.attachments[0]?.id) {
    return formData.value.attachments[0].id;
  }
  return null;
};

const resetForm = () => {
  formData.value = {
    id: null,
    title: "",
    attachments: [],
    fileList: [],
  };
  isUploading.value = false;
};

const handleSubmit = async () => {
  formRef.value?.validate(async (valid) => {
    if (!valid) return;
    
    if (!validateFileUpload()) return;

    const title = formData.value.title.trim();
    if (!title) {
      ElMessage.warning("请输入标题");
      return;
    }

    const fileId = getFileId();
    if (!fileId) {
      ElMessage.warning(formData.value.id ? "请上传文件或保留原有文件" : "请先上传文件");
      return;
    }

    try {
      if (formData.value.id) {
        // 编辑
        await updateKnowledge(formData.value.id, fileId, title);
        ElMessage.success("更新成功");
      } else {
        // 新增
        await createKnowledge(fileId, title);
        ElMessage.success("新增成功");
        if (pagination.value.page !== 1) {
          pagination.value.page = 1;
        }
      }
      
      dialogVisible.value = false;
      resetForm();
      loadKnowledgeList();
    } catch (error) {
      console.error(formData.value.id ? "更新知识库失败" : "创建知识库失败", error);
      ElMessage.error(`${formData.value.id ? "更新" : "创建"}知识库失败，请重试`);
    }
  });
};

// ==================== 文件上传 ====================
const handleExceed = () => {
  ElMessage.warning("只能上传一个文件");
};

const beforeUpload = (file) => {
  const fileName = file.name.toLowerCase();
  const fileExtension = fileName.substring(fileName.lastIndexOf("."));
  
  if (!ALLOWED_EXTENSIONS.includes(fileExtension)) {
    ElMessage.error("不支持的文件格式，请上传 word/excel/pdf/ppt/txt 格式的文件");
    return false;
  }
  
  if (file.size > MAX_FILE_SIZE) {
    ElMessage.error("文件大小不能超过 100MB");
    return false;
  }
  
  return true;
};

const handleRemove = (file, fileList) => {
  const attachmentId = file?.response?.id;
  if (attachmentId !== undefined) {
    formData.value.attachments = formData.value.attachments.filter(
      (item) => item.id !== attachmentId
    );
  }
  formData.value.fileList = fileList;
};

const handleUploadRequest = async (options) => {
  const { file, onSuccess, onError } = options;
  isUploading.value = true;
  try {
    const response = await uploadKnowledgeAttachment(file);
    onSuccess(response);
  } catch (error) {
    ElMessage.error("上传失败，请重试");
    onError(error);
  } finally {
    isUploading.value = false;
  }
};

const handleUploadSuccess = (response, uploadFile, uploadFiles) => {
  const attachment = normalizeAttachment(response);
  uploadFile.response = attachment;
  uploadFile.status = "success";
  uploadFile.uid = String(attachment.id);
  uploadFile.name = attachment.filename;
  formData.value.attachments = [
    ...formData.value.attachments.filter((item) => item.id !== attachment.id),
    attachment,
  ];
  formData.value.fileList = uploadFiles;

  // 新增模式且标题为空时，自动使用文件名（去掉扩展名）作为标题
  if (formData.value.id === null && !formData.value.title?.trim()) {
    const autoTitle = extractTitleFromFilename(attachment.filename);
    if (autoTitle) {
      formData.value.title = autoTitle;
    }
  }

  ElMessage.success("上传成功");
};

const handleUploadError = (error, uploadFile, uploadFiles) => {
  ElMessage.error("上传失败，请稍后重试");
  formData.value.fileList = uploadFiles;
};

// ==================== 其他操作 ====================
const goBack = () => {
  router.push("/");
};

// ==================== 生命周期 ====================
onMounted(() => {
  loadKnowledgeList();
});
</script>

<style scoped>
.knowledge-base-container {
  height: 100vh;
  background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
  padding: 20px;
  position: relative;
  display: flex;
  flex-direction: column;
  overflow: hidden;
}

.back-button {
  position: fixed;
  top: 20px;
  left: 20px;
  display: flex;
  align-items: center;
  gap: 8px;
  padding: 10px 16px;
  background: rgba(255, 255, 255, 0.95);
  color: #333;
  border: 1px solid rgba(255, 255, 255, 0.3);
  border-radius: 20px;
  cursor: pointer;
  font-size: 14px;
  font-weight: 500;
  box-shadow: 0 4px 15px rgba(0, 0, 0, 0.1);
  transition: all 0.3s ease;
  z-index: 1000;
}

.back-button:hover {
  background: #ffffff;
  transform: translateX(-2px);
  box-shadow: 0 6px 20px rgba(0, 0, 0, 0.15);
}

.back-button svg {
  width: 18px;
  height: 18px;
}

.knowledge-base-content {
  max-width: 1200px;
  margin: 0 auto;
  background: #ffffff;
  border-radius: 12px;
  padding: 24px;
  box-shadow: 0 8px 32px rgba(0, 0, 0, 0.1);
  display: flex;
  flex-direction: column;
  height: 100%;
  max-height: calc(100vh - 40px);
  overflow: hidden;
}

.search-section {
  display: flex;
  gap: 12px;
  margin-bottom: 24px;
  align-items: center;
  flex-shrink: 0;
}

.search-input {
  flex: 1;
  max-width: 500px;
}

.table-section {
  flex: 1;
  display: flex;
  flex-direction: column;
  min-height: 0;
  overflow: hidden;
}

.table-wrapper {
  flex: 1;
  overflow: auto;
  min-height: 0;
}

.pagination-wrapper {
  display: flex;
  justify-content: flex-end;
  margin-top: 20px;
  padding: 20px 0;
  flex-shrink: 0;
}

.add-button-wrapper {
  display: flex;
  justify-content: center;
  margin-top: 24px;
  flex-shrink: 0;
  padding-bottom: 0;
}

.add-button {
  padding: 12px 32px;
  font-size: 16px;
}

.upload-demo {
  width: 100%;
}

.dialog-footer {
  display: flex;
  justify-content: flex-end;
  gap: 12px;
}

:deep(.el-table) {
  font-size: 14px;
}

:deep(.el-table th) {
  background-color: #f5f7fa;
  color: #606266;
  font-weight: 600;
}

:deep(.el-table--border) {
  border: 1px solid #dcdfe6;
}

:deep(.el-table--stripe .el-table__body tr.el-table__row--striped td) {
  background-color: #fafafa;
}

:deep(.el-button--small) {
  padding: 5px 15px;
}

.file-info-cell {
  display: flex;
  flex-direction: column;
  gap: 6px;
}

.file-name-row {
  display: flex;
  align-items: center;
  gap: 6px;
}

.file-icon {
  color: #409eff;
  font-size: 16px;
}

.file-name {
  font-weight: 500;
  color: #303133;
  overflow: hidden;
  text-overflow: ellipsis;
  white-space: nowrap;
  max-width: 200px;
}

.file-meta-row {
  display: flex;
  align-items: center;
  gap: 8px;
  font-size: 12px;
  color: #909399;
}

.file-type {
  color: #67c23a;
  font-weight: 500;
}

.file-separator {
  color: #dcdfe6;
}

.file-date {
  color: #909399;
}

.no-file {
  color: #c0c4cc;
  font-style: italic;
}
</style>
